package com.zimmur.service.impl.order;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import com.google.common.base.Throwables;
import com.zimmur.common.AppModuleEnum;
import com.zimmur.common.IDWorkFactory;
import com.zimmur.common.PointConvert;
import com.zimmur.dao.order.IOrderDao;
import com.zimmur.dao.order.IOrderDetailDao;
import com.zimmur.dao.order.IPayExpressDao;
import com.zimmur.model.account.AccountInfo;
import com.zimmur.model.account.CouponDetail;
import com.zimmur.model.account.UserAddress;
import com.zimmur.model.base.Express;
import com.zimmur.model.goods.Goods;
import com.zimmur.model.goods.GoodsSize;
import com.zimmur.model.order.Order;
import com.zimmur.model.order.OrderCoupon;
import com.zimmur.model.order.OrderDetail;
import com.zimmur.model.order.PayExpress;
import com.zimmur.model.order.view.OrderParameter;
import com.zimmur.model.order.view.ReceiveOrderListModel;
import com.zimmur.model.order.view.ReceiveOrderModel;
import com.zimmur.service.IAccountInfoService;
import com.zimmur.service.account.ICouponService;
import com.zimmur.service.account.IUserAddressService;
import com.zimmur.service.base.IExpressService;
import com.zimmur.service.goods.IGoodsOrganizationService;
import com.zimmur.service.goods.IGoodsService;
import com.zimmur.service.goods.IGoodsSizeService;
import com.zimmur.service.order.ICartService;
import com.zimmur.service.order.IOrderCouponService;
import com.zimmur.service.order.IOrderService;
import com.zimmur.service.order.IPayExpressService;
import com.zimmur.tools.DateUtils;
import com.zimmur.tools.PageUtil;
import com.zimmur.tools.PreciseCompute;

@Service("orderServiceImpl")
public class OrderServiceImpl implements IOrderService {
	private Logger log = LoggerFactory.getLogger(OrderServiceImpl.class);
	
	@Resource
	private IAccountInfoService accountInfoService;
	
	@Resource
	private IGoodsService goodsService;
	
	@Resource
	private IGoodsSizeService goodsSizeService;
	
	@Autowired
	private IOrderDetailDao orderDetailDao;
	
	@Resource
	private IOrderDao orderDao;
	@Resource
	private IPayExpressDao payExpressDao;
	
	@Resource
	private IUserAddressService userAddressService;
	
	@Resource
	private IExpressService expressService;
	
	@Resource
	private IPayExpressService payExpressService;
	
	@Resource
	private ICartService cartService;
	@Resource
	private IGoodsOrganizationService goodsOrganizationService;
	@Resource
	private IOrderCouponService orderCouponService;
	@Resource 
	private ICouponService couponService;
	
	@Transactional(propagation=Propagation.REQUIRES_NEW,rollbackFor = {RuntimeException.class,Exception.class})
	public long createOrder(ReceiveOrderListModel listModel,long userId,Integer source){
		/**
		 * 订单总价
		 */
		double countPrice = 0;
		/**
		 * 标准总价
		 */
		double countStandardPrice=0;
		/**
		 * 优惠金额
		 */
		double shareJe=0;
		int orderNum = 0;
		if(listModel.getOrderCollocations().isEmpty()){
			return 0;
		}
		
		List<OrderDetail> orderDetails = new ArrayList<OrderDetail>();
		
		String goodsId;
		int quantity=0;
		long sizeCode = 0;
		long lGoodsId = 0;
		
		long orderId;
		//折扣
		double discount=1;
		CouponDetail couponDetail=null;
		try{
			if(listModel.getCouponId()!=0){
				couponDetail=couponService.selectCouponByCouponId(listModel.getCouponId());
				if(couponDetail != null && !"2".equals(couponDetail.getCouponState())){
					return -2;//优惠券已失效
				}
				if(couponDetail!=null && "discount".equals(couponDetail.getCouponStockType())){
					if(couponDetail.getCouponDiscount()>0 && couponDetail.getCouponDiscount()<100){
						discount=PreciseCompute.div(couponDetail.getCouponDiscount(), 100.00, 2);
					}
				}
				
			}
			orderId = IDWorkFactory.getID(AppModuleEnum.Order);
			
			int nowTime = DateUtils.getNowUnixTime();
			//是否开票
			Integer isInvoice = listModel.getIsInvoice();
			//开票姓名
			String invoiceName = listModel.getInvoiceName();
			//送货地址ID
			Long addrId = listModel.getAddressId();
			if(addrId == null){
				return 0;
			}
				
			//支付方式 wxpay/alipay
			//String payMethod = listModel.getPayMethod();
			//积分兑换
			Integer point = listModel.getPoint();
			if(point == null)
				point = 0; 
			// 订单备注
			String orderRemark = listModel.getRemark();
			if(orderRemark.equals(""))
				orderRemark = "";
			//expressCode
			String expressCode = listModel.getExpressCode();
			if("".equals(expressCode)){
				Express express = expressService.selectDefaultExpress();
				if(express != null){
					expressCode = express.getExpressCode();
				}
			}
			Express express= expressService.selectByExpressCode(expressCode);
			// 快递费用
			double expressFee =express.getTopPrice().doubleValue();

			AccountInfo userAccountInfo = accountInfoService.selectByUserId(userId);
			if(userAccountInfo.getCurPoint()<point){
				return 0;
			}
			//订单类型 1=商品/2=家定/3=配饰
			int iOrderType = 1;
			/**
			 * 0=现货 1=预售
			 */
			Integer isPrepay=0;
			for (ReceiveOrderModel model : listModel.getOrderCollocations()) {
				goodsId = model.getGoodsId();
				sizeCode = Long.parseLong(model.getSizeCode());
				quantity = model.getQuantity();
				isPrepay = model.getIsPrepay();
				if (!goodsId.equals("") && sizeCode>0 && quantity > 0) {
					lGoodsId = Long.parseLong(goodsId);
					Goods goodsModel = goodsService.selectByGoodsId(lGoodsId);
					if(goodsModel.getTypeFlag()==3){
						iOrderType=3;
					}
					GoodsSize goodsSizeModel = goodsSizeService.selectbySizeId(sizeCode);
					if (goodsModel != null && goodsSizeModel != null) {
						double modelPrice = isPrepay == 1 ? goodsModel.getPrepayPrice().doubleValue()
								: goodsModel.getPrice().doubleValue();
						if(iOrderType != goodsModel.getTypeFlag()){
							iOrderType = goodsModel.getTypeFlag();
						}
						OrderDetail orderDetail = new OrderDetail();
						orderDetail.setOrderDetailId(IDWorkFactory.getID(AppModuleEnum.Order)+"");
						orderDetail.setOrderId(orderId+"");
						orderDetail.setGoodsId(lGoodsId+"");
						orderDetail.setOrderType(goodsModel.getTypeFlag());
						orderDetail.setUserId(userId+"");
						orderDetail.setSkuCode(goodsSizeModel.getSkuCode());
						orderDetail.setStyleCode(goodsModel.getStyleCode());
						orderDetail.setGoodsTitle(goodsModel.getTitle());
						orderDetail.setGoodsComment(
								goodsModel.getTitle() + " " + goodsSizeModel.getColor() + " " + goodsSizeModel.getSize());
						orderDetail.setGoodsSize(goodsSizeModel.getSize());
						orderDetail.setGoodsColor(goodsSizeModel.getColor());
						orderDetail.setStandardPrice(goodsModel.getStandardPrice().doubleValue());
						orderDetail.setPrice(modelPrice);
						orderDetail.setQuantity(quantity);
						orderDetail.setOrderDate(nowTime);
						orderDetail.setCoverImage(goodsModel.getCoverImage());
						orderDetail.setSizeCode(goodsSizeModel.getSizeCode());
						orderDetail.setIsPrepay(isPrepay.shortValue());
						orderDetail.setOffPercent(goodsModel.getOffPercent());
						orderDetails.add(orderDetail);

						countStandardPrice += PreciseCompute.mul(goodsModel.getStandardPrice().doubleValue(), quantity);
						countPrice += PreciseCompute.mul(modelPrice, quantity);
						orderNum += 1;
						
					}
				}

			}
			if(couponDetail!=null && "cash".equals(couponDetail.getCouponStockType())){
				shareJe=PreciseCompute.div(couponDetail.getCouponValue(), 100.00, 2);
				countPrice=PreciseCompute.sub(countPrice, shareJe);
//				double flag=PreciseCompute.div(couponValue, countPrice, 2);
//				double goodsSharePrice=0;
//				for(OrderDetail orderDetail:orderDetails){
//					double couponfee=PreciseCompute.mul(flag, orderDetail.getPrice());
//					goodsSharePrice=PreciseCompute.sub(orderDetail.getPrice(), couponfee);
//					goodsSharePrice=PreciseCompute.round(goodsSharePrice, 2);
//					orderDetail.setSharePrice(goodsSharePrice);
//				}
			}
			if(couponDetail!=null && "discount".equals(couponDetail.getCouponStockType())){
				shareJe=PreciseCompute.mul(countPrice, discount);
				countPrice=PreciseCompute.sub(countPrice, shareJe);
			}
//			if(couponDetail==null){
//				sharePrice=countPrice;
//			}
			if (!orderDetails.isEmpty()) {
				double pointJe = 0;
				
				countStandardPrice = PreciseCompute.round(countStandardPrice, 2);
				countPrice = PreciseCompute.round(countPrice, 2);
				shareJe=PreciseCompute.round(shareJe, 2);
				
				Order order = new Order();
				order.setOrderId(orderId+"");
				order.setOrderType(iOrderType);
				order.setUserId(userId);
				order.setRemark(orderRemark);
				order.setStandardPrice(countStandardPrice);
				order.setPrice(countPrice);
				order.setExpressFee(expressFee);
				order.setSharePrice(shareJe);
				order.setSource(source);
				if(couponDetail!=null){
					order.setIsusedCoupon((short)1);
				}
				double orderJe = PreciseCompute.add(countPrice, expressFee);
				//计算积分抵扣
				if(point > 0){
					pointJe = PointConvert.pointToJe(point);
					orderJe = PreciseCompute.sub(orderJe, pointJe);
				}
				order.setPoint(point);
				order.setPointJe(pointJe);
				if(orderJe<0){
					return 0;
				}
				order.setOrderJe(PreciseCompute.round(orderJe, 2));
				if(iOrderType==1 ||iOrderType==2||iOrderType==3){
					order.setOderStatus("00");
				}
				order.setOrderStatusText("待付款");
				order.setCreateDate(nowTime);
				order.setOrderNum(orderNum);
				
				int iRet = orderDao.insertSelective(order);
				if (iRet > 0) {
					//扣减积分
					//accountInfoService.updateCurPointByUserId(userId, (point*-1), "订单:"+orderId+" 支付抵扣");
					//添加订单详情
					orderDetailDao.insertBatch(orderDetails);
				}
				if(couponDetail!=null){
					try {
						//更新优惠券详情和批次信息
						couponDetail.setUseTime(DateUtils.getNowUnixTime());
						couponDetail.setDataId(orderId+"");
						couponDetail.setCouponState("4");//优惠券已锁定
						couponDetail.setCouponUseValue(PreciseCompute.doubleToInt(shareJe));
						couponService.updateCoupon(couponDetail);
						couponService.updateCouponStock(couponDetail.getCouponStockId(), 0, 0, 1);
						//添加订单使用的优惠券记录
						OrderCoupon orderCoupon=new OrderCoupon(orderId, couponDetail.getCouponId(), couponDetail.getCouponStockId(),
								couponDetail.getChannelId(),couponDetail.getCouponName(),couponDetail.getCouponStockType(),
								couponDetail.getCouponValue(),couponDetail.getCouponDiscount(),couponDetail.getCouponMininum(),
								DateUtils.getNowUnixTime(),couponDetail.getCouponUseValue(),couponDetail.getMobileNo(),
								couponDetail.getCouponCode());
						orderCouponService.add(orderCoupon);
					} catch (Exception e) {
						log.error(e.getMessage(),e);
						
					}
				}
				//begin 添加收货信息
				UserAddress userAddress = userAddressService.selectById(addrId);
				
				
				PayExpress payExpress = new PayExpress();
				payExpress.setIsInvoice(isInvoice);
				payExpress.setInvoiceName(invoiceName);
				payExpress.setOrderId(orderId+"");
				payExpress.setUserName(userAddress.getContactName());
				payExpress.setShipProvince(userAddress.getProvince());
				payExpress.setShipCity(userAddress.getCity());
				payExpress.setShipArea(userAddress.getArea());
				payExpress.setShipStreet(userAddress.getStreet());
				payExpress.setShipPostcode("");
				payExpress.setShipMobile(userAddress.getTel());
				payExpress.setShipMethod(express.getExpressCode());
				payExpress.setShipCompany(express.getExpressName());
				payExpress.setShipNo("");
				payExpress.setReserveUserName(listModel.getReserveUserName());
				payExpress.setReserveMobile(listModel.getReserveMobile());
				payExpress.setReserveGender(listModel.getReserveGender());
				payExpress.setReserveTime(listModel.getReserveTime());
				
				payExpressService.insert(payExpress);
				//end 添加收货信息
				listModel.setOrderJe(orderJe);
				//非闪创商品清除购物车，处理库存
				try {
					cartService.delCart(userId, listModel.getOrderCollocations());
					// 商品销售数及订单数增加,库存占用处理
					goodsSizeService.mainGoodsInventory(orderId);
				} catch (Exception e) {
					log.error(e.getMessage());
				}
				
			}else{
				orderId=-1;
			}
		}catch(Exception e){
			log.error(e.getMessage(),e);
			orderId=-1;
			Throwables.propagate(e);
			
		}
		return orderId;
	}

	/**
	 * 更新订单状态
	 * @param orderId	 
	 * @param transactonId 付款单号
	 * @param payJe 付款金额
	 * @param orderStatus 00=待付款/10=已付款待发货/20=已发货待完成/30=已完成/90=订单取消,41=参闪待付款/42=参闪已付款/43=参闪待发货/44=参闪待收货/45=参闪已完成/46=参闪待退款/47=参闪已退款/48=参闪申请退款
	 * @param orderStatusText 订单状态描述
	 * @return
	 */
	@Transactional(propagation=Propagation.REQUIRES_NEW,rollbackFor={RuntimeException.class,Exception.class})
	public boolean updateOrderStatusByPayNotify(long orderId,String payMethod,String transactonId,double payJe,String orderStatus,String orderStatusText) {
		boolean bRet = false;
		if(orderId>0 && !orderStatus.equals("")){
			
			Map<String, Object> map = new HashMap<>();
			map.put("orderId", orderId);
			map.put("payMethod", payMethod);
			map.put("transactionId", transactonId);
			map.put("payDate", DateUtils.getNowUnixTime());
			map.put("payJe", payJe);
			map.put("orderStatus", orderStatus);
			map.put("orderStatusText", orderStatusText);
			
			
			bRet = orderDao.updateOrderStatusByPayForOrderId(map)>0?true:false;
			if (bRet && payJe > 0) {
				Order order = selectByOrderId(orderId);
				bRet = calcOrderSharePrice(orderId,order.getOrderJe(),payJe);
			}
		}
		return bRet;
	}
	/**
	 * 计算订单明细均摊费用
	* @Title: calcOrderSharePrice 
	* @Description: 计算订单明细均摊费用
	* @param orderId
	* @param payJe
	* @return boolean    返回类型
	 */
	private boolean calcOrderSharePrice(long orderId,double orderJe,double payJe){
		boolean result = false;
		double realPayJe = payJe;
		List<OrderDetail> orderDetailList = orderDetailDao.selectByOrderId(orderId);
		for (int i=0;i<orderDetailList.size();i++) {
			OrderDetail item = orderDetailList.get(i);
			if(i != orderDetailList.size()-1){
				double itemAmount = item.getPrice()*item.getQuantity();
				double sharePrice = payJe* PreciseCompute.div(itemAmount,orderJe, 1);
				
				item.setShareAmount(sharePrice);
				realPayJe = PreciseCompute.sub(realPayJe, sharePrice);
			}else{
				item.setShareAmount(realPayJe);
			}
			result = orderDetailDao.updateByPrimaryKeySelective(item)>0;
		}
		return result;
	}
	@Override
	public boolean updateOrderStatus(long orderId, String orderStatus, String reasonText) {
		if(orderId>0 && !orderStatus.equals("")){
			Map<String, Object> map = new HashMap<>();
			map.put("orderId", orderId);
			map.put("orderStatus", orderStatus);
			map.put("reasonText", reasonText);
			
			return orderDao.updateOrderStatusByOrderId(map)>0?true:false;
		}
		return false;
	}
	@Override
	public Order selectByOrderId(long orderId) {
		return orderDao.selectByPrimaryKey(orderId);
	}

	@Override
	public int deleteByPrimaryKey(Long orderid) {
		return orderDao.deleteByPrimaryKey(orderid);
	}

	@Override
	public PageUtil<Order> selectByOderStatusList(OrderParameter orderParameter) {
		List<Order>  filterOrderList  = new ArrayList<Order>();
		PageUtil<Order> page = new PageUtil<>();
		try {
			Integer totalRecord = orderDao.selectByOrderStatusCount(orderParameter);
			//订单信息  没有明细 则不显示订单
			List<Order> orderListS = orderDao.selectByOrderStatusList(orderParameter);
			
			if(!orderListS.isEmpty() && orderListS.size() > 0){
				for(Order orderItem : orderListS){
					//订单明细
					List<OrderDetail> orderDetailList = orderDetailDao.selectByOrderIdAndGoodsTitle(Long.parseLong(orderItem.getOrderId()),orderParameter.getGoodsTitle());
					if(!orderDetailList.isEmpty()){
						orderItem.setOrderDetailList(orderDetailList);
						//订单支付及收货信息
						PayExpress payExpress = payExpressDao.selectByPrimaryKey(Long.parseLong(orderItem.getOrderId()));
						if(payExpress != null){
							orderItem.setPayExpress(payExpress);
						}
						filterOrderList.add(orderItem);
					}else{
						totalRecord -=1;
					}
				}
			}
			if(!filterOrderList.isEmpty() && filterOrderList.size() > 0){
				page.setTotalRecord(totalRecord);
				page.setPageNo(orderParameter.getPageNo());
				page.setItemList(filterOrderList);
			}
		} catch (Exception e) {
			log.error(e.getMessage());
			throw new RuntimeException(e.getMessage());
		}
		return page;
	}
	@Override
	public PageUtil<Order> selectOrganizationOrder(OrderParameter orderParameter) {
		List<Order> orderList = new ArrayList<>();
		PageUtil<Order> page = new PageUtil<>();
		List<Order> orderListS =null;
		try {
			Integer totalRecord = orderDao.countOrganizationOrder(orderParameter);
			if (totalRecord>0) {
				orderParameter.setTotalRecord(totalRecord);
				orderListS = orderDao.selectOrganizationOrder(orderParameter);
			}
			if(orderListS!=null && orderListS.size() > 0){
				for(Order orderItem : orderListS){
					//订单明细
					List<OrderDetail> orderDetailList = orderDetailDao.selectByOrderIdAndIsService(Long.parseLong(orderItem.getOrderId()));
					if(orderDetailList!=null && orderDetailList.size()>0 ){
						orderItem.setOrderDetailList(orderDetailList);
						//闪创商品信息
						/*GoodsOrganization goodsOrganization=goodsOrganizationService.selectByGoodsId(Long.parseLong(orderDetailList.get(0).getGoodsId()));
						if(goodsOrganization!=null){
							orderDetailList.get(0).setGoodsOrganization(goodsOrganization);
						}*/
					}
					//订单支付及收货信息
					PayExpress payExpress = payExpressDao.selectByPrimaryKey(Long.parseLong(orderItem.getOrderId()));
					if(payExpress != null){
						orderItem.setPayExpress(payExpress);
					}
					if(!orderDetailList.isEmpty()){
						orderList.add(orderItem);
					}
				}
			}
			if( orderList.size() > 0){
				page.setTotalRecord(totalRecord);
				page.setItemList(orderList);
			}
		} catch (Exception e) {
			log.error(e.getMessage());
			throw new RuntimeException(e.getMessage());
		}
		return page;
	}

	@Override
	public int updateByPrimaryKeySelective(Order record) {
		return orderDao.updateByPrimaryKeySelective(record);
	}
	
	@Override
	public List<Order> selectListByTimeOut(int unixTime) {
		return orderDao.selectListByTimeOut(unixTime);
	}
	@Override
	public boolean updateOrderStatusToCancelByOrderId(long orderId) {
		return orderDao.updateOrderStatusByOutTime(orderId)>0?true:false;
	}

	@Override
	public List<Order> selectOrderByGoodsIdAndStatus(long goodsId, String orderStatus) {
		List<Order> orders=orderDao.selectOrganizationOrderByGoodsId(goodsId, orderStatus);
		return orders;
	}

	@Override
	public int updateOrderByOrderIds(String orderStatus, String orderStatusText, List<Long> orderIds) {
		int flag=orderDao.updateOrderByOrderIds(orderStatus, orderStatusText, orderIds);
		return flag;
	}

	@Override
	public List<Long> selectServiceOrderIDByParam(OrderParameter orderParameter) {
		
		return orderDao.selectServiceOrderIDByParam(orderParameter);
	}

	@Override
	public int countServiceOrderIDByParam(OrderParameter orderParameter) {
		
		return orderDao.countServiceOrderIDByParam(orderParameter);
	}

	@Override
	public List<Order> selectOrderByShipDateOut(int time) {
		List<Order> orders=orderDao.selectOrderByshipDate(time);
		return orders;
	}

	@Override
	public Order selectByOrderDetailIdAndUserId(Long orderId, Long userId) {
		//1.查询订单信息
		Order order = orderDao.selectByPrimaryKey(orderId);
		if(order!=null && order.getUserId().equals(userId)){
			//2.查询订单明细
			List<OrderDetail> orderDetailList = orderDetailDao.selectByOrderId(orderId);
			if(orderDetailList!=null&&!orderDetailList.isEmpty()){
				order.setOrderDetailList(orderDetailList);
			}
			//3.查询快递信息
			PayExpress payExpress = payExpressDao.selectByPrimaryKey(orderId);
			if(payExpress != null){
				order.setPayExpress(payExpress);
			}
		}
		return order;
	}

	
}
